package layers.agents;

import layers.physical.Crossroad;
import layers.physical.Path;
import layers.physical.Road;
import layers.physical.Truck;

import commands.EnterCrossroadCommand;
import commands.LeaveCrossroadCommand;
import commands.MoveForwardCommand;

import events.packageEvents.PackageDeliveredEvent;
import events.truckEvents.TruckEndedDrivingToDestinationEvent;
import events.truckEvents.TruckStartedDrivingToDestinationEvent;
import framework.events.EventBroker;

public class TruckAgentStateDrivingToDestination extends TruckAgentState {

	private Path path;
	
	public TruckAgentStateDrivingToDestination(TruckAgent agent, Path path) {
		super(agent);
		if(path == null){
			this.getAgent().clearPackageAgent();
			this.getAgent().setState(new TruckAgentStateCreatingIntention(getAgent()));
			this.clearAgent();
		}else{
			this.path = path;
			EventBroker.getEventBroker().notifyAll(new TruckStartedDrivingToDestinationEvent(this.getAgent().getTruck()));
		}
	}
	
	protected void processTick(){
		Truck truck = this.getAgent().getTruck();
		if (truck.allCommandsProcessed()) {
			if(!path.isAtLast(truck) || !truck.isOnConnector()){
				if (truck.isOnConnector()) {
					Crossroad cr1 = truck.getConnectorPosition().getConnector();
					Crossroad cr2 = path.getCrossroadNextTo(cr1);
					Road road = cr1.getConnectionTo(cr2);
					truck.addCommand(new LeaveCrossroadCommand(truck, road), this.getAgent());
					this.getAgent().setLastCr(cr1);
				} else if (truck.isOnConnection() && truck.getConnectionPosition().getConnection().isAtEnd(truck)) {
					truck.addCommand(new EnterCrossroadCommand(truck), this.getAgent());
				} else if (truck.isOnConnection() && !truck.getConnectionPosition().getConnection().isAtEnd(truck)) {
					truck.addCommand(new MoveForwardCommand(truck), this.getAgent());
				}
			}else{
				dropPackage();
			}
		}
	}
	
	protected void dropPackage(){
		EventBroker.getEventBroker().notifyAll(new PackageDeliveredEvent(this.getAgent().getPackageAgent()));
		this.getAgent().clearPackageAgent();
		this.getAgent().setState(new TruckAgentStateCreatingIntention(getAgent()));
		EventBroker.getEventBroker().notifyAll(new TruckEndedDrivingToDestinationEvent(this.getAgent().getTruck()));
		this.clearAgent();
	}
	
	protected void rejectIntention(Path path){
		//NO-OP
	}
}
